/*
@hehung
2023-2-8
转载请注明出处，版权由@hehung所有
email: 1398660197@qq.com
wechat: hehung95
*/

/*******************************************************************************
* Header include
******************************************************************************/
#include "hal_data.h"
#include "app_hw_i2c.h"
#include "app_isl29035.h"


#define ISL29035_DEBUG
#undef ISL29035_DEBUG

#ifdef ISL29035_DEBUG
#include <stdio.h>
#define LOG(fmt, ...) 	                printf(fmt, ##__VA_ARGS__)
#else
#define LOG(fmt, ...)
#endif 

/*******************************************************************************
* Macro Definitions
******************************************************************************/
#define ISL29035_I2C_SLAVE_ADDR_7BIT           (0x44U)

#define ISL29035_COMMAND_1_ADDR                (0x00U)
#define ISL29035_COMMAND_2_ADDR                (0x01U)
#define ISL29035_DATA_L_ADDR                   (0x02U)
#define ISL29035_DATA_H_ADDR                   (0x03U)
#define ISL29035_INT_LT_LSB_ADDR               (0x04U)
#define ISL29035_INT_LT_MSB_ADDR               (0x05U)
#define ISL29035_INT_HT_LSB_ADDR               (0x06U)
#define ISL29035_INT_HT_MSB_ADDR               (0x07U)
#define ISL29035_ID_ADDR                       (0x0FU)

/* 10100000: enable ALS consinuously  */
#define ISL29035_COMMAND_1_INIT                (0xA0U)
/* 00000110: Lux full scale range is 4000 and ADC  */
#define ISL29035_COMMAND_2_INIT                (0x06U)

/*******************************************************************************
* Static Variables Definitions 
******************************************************************************/
static int32_t Isl29035_Resolution = ISL29035_RES_8BIT;
static int32_t Isl29035_range = ISL29035_LUX_SCALE_4K;
static uint32_t Isl29035_data;

/*******************************************************************************
* Static Function Declarations 
******************************************************************************/
static void Isl29035_ReadFromI2C(uint8_t *data_buffer, uint8_t data_len);
static void Isl29035_WriteToI2C(uint8_t *data_buffer, uint8_t data_len);
static uint32_t Isl29035_DataConvert(uint32_t data);

/*******************************************************************************
* Function Definitions 
******************************************************************************/
/*********************Isl29035读数据函数************************************/
static void Isl29035_ReadFromI2C(uint8_t *data_buffer, uint8_t data_len)
{
	fsp_err_t err;
	uint32_t timeout_ms = 100;

   R_SCI_I2C_SlaveAddressSet(&g_sci2_i2c_ctrl, 
                            ISL29035_I2C_SLAVE_ADDR_7BIT, 
							I2C_MASTER_ADDR_MODE_7BIT);

	err = R_SCI_I2C_Read(&g_sci2_i2c_ctrl, data_buffer, data_len, true);
	assert(FSP_SUCCESS == err);
	
	/* Since there is nothing else to do, block until Callback triggers*/
	while ((I2C_MASTER_EVENT_TX_COMPLETE != sci3_i2c_event) && timeout_ms>0)
	{
		R_BSP_SoftwareDelay(1U, BSP_DELAY_UNITS_MICROSECONDS);
		timeout_ms--;
	}
	
	if (I2C_MASTER_EVENT_ABORTED == sci2_i2c_event)
	{
		// __BKPT(0);
		LOG ("Isl29035: sci2 i2c read event aborted occurred\n");
	}
	/* Read data back from the I2C slave */
	sci2_i2c_event = I2C_MASTER_EVENT_ABORTED;
}

/*********************Isl29035写数据函数************************************/
static void Isl29035_WriteToI2C(uint8_t *data_buffer, uint8_t data_len)
{
	fsp_err_t err;
	uint32_t timeout_ms = 100;

   R_SCI_I2C_SlaveAddressSet(&g_sci2_i2c_ctrl, 
                             ISL29035_I2C_SLAVE_ADDR_7BIT, 
							 I2C_MASTER_ADDR_MODE_7BIT);

	err = R_SCI_I2C_Write(&g_sci2_i2c_ctrl, data_buffer, data_len, true);
	assert(FSP_SUCCESS == err);
	
	/* Since there is nothing else to do, block until Callback triggers*/
	while ((I2C_MASTER_EVENT_TX_COMPLETE != sci2_i2c_event) && timeout_ms>0)
	{
		R_BSP_SoftwareDelay(1U, BSP_DELAY_UNITS_MICROSECONDS);
		timeout_ms--;
	}
	
	if (I2C_MASTER_EVENT_ABORTED == sci2_i2c_event)
	{
		// __BKPT(0);
		LOG ("Isl29035: sci2 i2c write event aborted occurred\n");
	}
	/* Read data back from the I2C slave */
	sci2_i2c_event = I2C_MASTER_EVENT_ABORTED;
}

static uint32_t Isl29035_DataConvert(uint32_t data)
{
   return (uint32_t)((double)Isl29035_range / (double)Isl29035_Resolution * data);
}

void Isl29035_Init(void)
{
   uint8_t command[2U];
   
   command[0] = ISL29035_COMMAND_1_ADDR;
   command[1] = ISL29035_COMMAND_1_INIT;
   Isl29035_WriteToI2C(command, 2);

   command[0] = ISL29035_COMMAND_2_ADDR;
   command[1] = ISL29035_COMMAND_2_INIT;
   Isl29035_WriteToI2C(command, 2);

   Isl29035_Resolution = ISL29035_RES_8BIT;
   Isl29035_range = ISL29035_LUX_SCALE_4K;
}

void Isl29035_StartSampling(void)
{
	uint8_t data;
	uint8_t address;
	uint16_t read_adc;

	/* Read low byte of data */
	address = ISL29035_DATA_L_ADDR;
	Isl29035_WriteToI2C(&address, 1);
	Isl29035_ReadFromI2C(&data, 1);
	read_adc = data;

	/* Read high byte of data */ 
	address = ISL29035_DATA_H_ADDR;
	Isl29035_WriteToI2C(&address, 1);
	Isl29035_ReadFromI2C(&data, 1);
	read_adc |= (data << 8U);

	Isl29035_data = Isl29035_DataConvert(read_adc);
}

uint32_t Isl29035_ReadData(void)
{
	return Isl29035_data;
}

